/*
 *  Copyright (c) 2011 Leibniz Institute of Plant Genetics and Crop Plant Research (IPK), Gatersleben, Germany.
 *  All rights reserved. This program and the accompanying materials
 *  are made available under the terms of the GNU Lesser Public License v2.1
 *  which accompanies this distribution, and is available at
 *  http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
 *
 *  Contributors:
 *      Leibniz Institute of Plant Genetics and Crop Plant Research (IPK), Gatersleben, Germany - initial API and implementation
 */
package de.ipk_gatersleben.bit.bi.edal.primary_data.metadata;

import javax.persistence.Column;

import org.hibernate.search.annotations.Field;
import org.hibernate.search.annotations.Index;
import org.hibernate.search.annotations.Store;

/**
 * Represent a natural person.
 * 
 * @author lange
 * @author arendd
 */
public class NaturalPerson extends Person {

	private static final long serialVersionUID = 6858824330148276157L;
	private String sureName;
	private String givenName;

	/**
	 * Constructor for a natural person with specified values.
	 * 
	 * @param sureName
	 *            sure name of the {@link Person}.
	 * @param givenName
	 *            given name of the {@link Person}.
	 * @param addressLine
	 *            address of the {@link Person}.
	 * @param zip
	 *            zip of the {@link Person}.
	 * @param country
	 *            country of the {@link Person}.
	 */
	public NaturalPerson(final String sureName, final String givenName,
			final String addressLine, final String zip, final String country) {
		super(addressLine, zip, country);
		this.sureName = sureName;
		this.givenName = givenName;
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see java.lang.Object#hashCode()
	 */
	@Override
	public int hashCode() {
		final int prime = 31;
		int result = super.hashCode();
		result = prime * result
				+ ((givenName == null) ? 0 : givenName.hashCode());
		result = prime * result
				+ ((sureName == null) ? 0 : sureName.hashCode());
		return result;
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see java.lang.Object#equals(java.lang.Object)
	 */
	@Override
	public boolean equals(Object obj) {
		if (this == obj)
			return true;
		if (!super.equals(obj))
			return false;
		if (getClass() != obj.getClass())
			return false;
		NaturalPerson other = (NaturalPerson) obj;
		if (givenName == null) {
			if (other.givenName != null)
				return false;
		} else if (!givenName.equals(other.givenName))
			return false;
		if (sureName == null) {
			if (other.sureName != null)
				return false;
		} else if (!sureName.equals(other.sureName))
			return false;

		return true;
	}

	/** {@inheritDoc} */
	@Override
	public int compareTo(final UntypedData datatype) {

		if (datatype instanceof NaturalPerson) {

			NaturalPerson naturalPerson = (NaturalPerson) datatype;

			if (givenName.compareTo(naturalPerson.givenName) == 0) {
				if (sureName.compareTo(naturalPerson.sureName) == 0) {
					return super.compareTo(naturalPerson);
				} else {
					return sureName.compareTo(naturalPerson.sureName);
				}
			} else {
				return givenName.compareTo(naturalPerson.givenName);
			}
		} else {
			return -1;
		}
	}

	/**
	 * Getter for the field <code>given_name</code>.
	 * 
	 * @return the given name
	 */
	@Column(columnDefinition = "varchar(4000)")
	@Field(index = Index.TOKENIZED, store = Store.YES)
	public String getGivenName() {
		return this.givenName;
	}

	/**
	 * Getter for the field <code>sure_name</code>.
	 * 
	 * @return the sure name
	 */
	@Column(columnDefinition = "varchar(4000)")
	@Field(index = Index.TOKENIZED, store = Store.YES)
	public String getSureName() {
		return this.sureName;
	}

	/**
	 * @param givenName
	 *            the givenName to set
	 */
	public void setGivenName(String givenName) {
		this.givenName = givenName;
	}

	/**
	 * @param sureName
	 *            the sureName to set
	 */
	public void setSureName(String sureName) {
		this.sureName = sureName;
	}

	/** {@inheritDoc} */
	@Override
	public String toString() {
		if (this.sureName.length() + this.givenName.length()
				+ this.getAddressLine().length() + this.getZip().length()
				+ this.getCountry().length() > 0) {
			return this.formatEmptyString(this.sureName) + ", "
					+ this.formatEmptyString(this.givenName) + ", "
					+ this.formatEmptyString(this.getAddressLine()) + ", "
					+ this.formatEmptyString(this.getZip()) + ", "
					+ this.formatEmptyString(this.getCountry());
		} else {
			return Person.UNKNOWN;
		}
	}

}
